/*
 * ParserRed.cpp
 *
 *  Created on: 05/05/2013
 *      Author: Juliansci
 */

#include "ParserRed.h"
#include <stdlib.h>
#include "../modelo/bonus/BonusBuilder.h"

Personaje* ParserRed::parsearPersonaje(Builder* builder, string data) {
	vector<string> datosParseados = this->parsearData('|', data);
	Personaje* personaje = new Personaje();

	string usuario = datosParseados.at(0);
	string tipo = datosParseados.at(1);
	int x = atoi(datosParseados.at(2).c_str());
	int y = atoi(datosParseados.at(3).c_str());
	int velocidad = atoi(datosParseados.at(4).c_str());
	string accion = datosParseados.at(5);
	int dx = atoi(datosParseados.at(6).c_str());
	int dy = atoi(datosParseados.at(7).c_str());
	int vida = atoi(datosParseados.at(8).c_str());
	int magia = atoi(datosParseados.at(9).c_str());
	//cout << "la vida que me llega es : " << vida << endl;
	personaje->setUsuario(usuario);
	TipoEntidad* tipoEntidad = builder->getTipoEntidad(tipo);
	personaje->setTipo(tipoEntidad);
	personaje->setCoordenadas(x, y);
	personaje->setdx(dx);
	personaje->setdy(dy);
	personaje->setVelocidad(velocidad);
	personaje->setAccion(accion);
	personaje->setVida(vida);
	personaje->setVidaMaxima(tipoEntidad->getVida());
	personaje->setMagia(magia);
	personaje->setMagiaMaxima(tipoEntidad->getMagia());
	personaje->setPasosVision(tipoEntidad->getPasosVision());
	if (accion.compare("frizado") == 0) {
		personaje->setActivo(false);
	} else {
		personaje->setActivo(true);
	}
	if (accion.compare("congelado") == 0) {
	//	cout << "esta congelado ahora" << endl;
		personaje->setCongelado(true);
	} else {
		personaje->setCongelado(false);
	}

	return personaje;

}

Personaje* ParserRed::parsearPersonajeUpdate(Builder* builder, string data) {
	vector<string> datosParseados = this->parsearData('|', data);
	Personaje* personaje = new Personaje();

	string usuario = datosParseados.at(0);
	int x = atoi(datosParseados.at(1).c_str());
	int y = atoi(datosParseados.at(2).c_str());
	int dx = atoi(datosParseados.at(3).c_str());
	int dy = atoi(datosParseados.at(4).c_str());
	string accionActual = datosParseados.at(5);

	personaje->setUsuario(usuario);
	personaje->setCoordenadas(x, y);
	personaje->setdx(dx);
	personaje->setdy(dy);
	personaje->setAccion(accionActual);

	return personaje;

}

vector<string> ParserRed::parsearData(char separador, string data) {
	vector<string> vectorDatos;
	istringstream iss(data);
	string dataActual = "";
	while (getline(iss, dataActual, separador) != NULL) {
		//cout << "dataActual: " << dataActual << endl;
		vectorDatos.push_back(dataActual);
	}
	return vectorDatos;
}

list<Personaje*> ParserRed::parsearPersonajes(Builder* builder, string data) {
	list<Personaje*> personajes;

	vector<string> personajesString = parsearData('*', data);
	vector<string>::iterator itPersonajesString = personajesString.begin();
	string personajeActualStringData;
	Personaje* personajeActual;
	for (; itPersonajesString != personajesString.end(); ++itPersonajesString) {
		personajeActualStringData = *itPersonajesString;
		personajeActual = parsearPersonaje(builder, personajeActualStringData);
		personajes.push_back(personajeActual);
	}
	return personajes;
}

list<pair<int, int> > ParserRed::parsearPosicionesVisitadas(string posiciones) {
	list<pair<int, int> > listaPosicionesVisitadas;
//	cout << "antes posiciones coordenadas" << endl;

	vector<string> posicionesCoordenadas = parsearData('*', posiciones);
	//cout << "desp posiciones coordenadas" << endl;
	vector<string>::iterator itPosicionesCoordenadas =
			posicionesCoordenadas.begin();
	vector<string> coordenadasActual;
	string posicionCoordenadaActual;
	//cout << "desp posiciones coordenadas antes for" << endl;

	for (; itPosicionesCoordenadas != posicionesCoordenadas.end();
			++itPosicionesCoordenadas) {

		posicionCoordenadaActual = *itPosicionesCoordenadas;

		coordenadasActual = parsearData('|', posicionCoordenadaActual);
		int x = atoi(coordenadasActual.at(0).c_str());
		int y = atoi(coordenadasActual.at(1).c_str());
		pair<int, int> coordenada;
		coordenada.first = x;
		coordenada.second = y;
		listaPosicionesVisitadas.push_back(coordenada);
	}
	return listaPosicionesVisitadas;
}

list<Entidad*> ParserRed::parsearEntidades(Builder* builder, string data) {
	list<Entidad*> entidades;
	vector<string> entidadesString = parsearData('*', data);
	vector<string>::iterator itEntidadesString = entidadesString.begin();
	string entidadActualStringData;
	Entidad* entidadActual;
	for (; itEntidadesString != entidadesString.end(); ++itEntidadesString) {
		entidadActualStringData = *itEntidadesString;
		entidadActual = parsearEntidad(builder, entidadActualStringData);
		entidades.push_back(entidadActual);
	}
	return entidades;
}

Entidad* ParserRed::parsearEntidad(Builder* builder, string data) {
	vector<string> datosParseados = this->parsearData('|', data);
	Entidad* entidad = new Entidad();

	int id = atoi(datosParseados.at(0).c_str());
	int vida = atoi(datosParseados.at(1).c_str());
	string nombreDestructor = datosParseados.at(2);
	entidad->setId(id);
	entidad->setVida(vida);
	entidad->setNombreDestructor(nombreDestructor);

	return entidad;

}

Bonus* ParserRed::parsearBonus(Builder* builder, string data){
	BonusBuilder bonusBuilder;
	vector<string> datosParseados = this->parsearData('|', data);
	int id = atoi(datosParseados.at(0).c_str());
	string nombre = datosParseados.at(1);
	int x = atoi(datosParseados.at(2).c_str());
	int y = atoi(datosParseados.at(3).c_str());
	Bonus* bonus = bonusBuilder.obtenerBonusNombre(nombre);
	bonus->setId(id);
	bonus->setCoordenadas(x,y);
	return bonus;

}
list<Bonus*> ParserRed::parsearListaBonus(Builder* builder, string data){
	list<Bonus*> listaBonus;
	vector<string> bonusString = parsearData('*', data);
	vector<string>::iterator itBonusString  = bonusString.begin();
	string bonusActualStringData;
	Bonus* bonusActual;
	for (; itBonusString != bonusString.end(); ++itBonusString) {
		bonusActualStringData = *itBonusString;
	//	cout << "bonus a parsear: " << bonusActualStringData << endl;
		bonusActual = parsearBonus(builder, bonusActualStringData);
	//	cout << "despues bonus a parsear: " << bonusActual->getId() << " nombre: " << bonusActual->getNombre()<< endl;

		listaBonus.push_back(bonusActual);
	}
	return listaBonus;
}
